<script setup>
defineOptions({
  name: 'MCountdown'
})
import { ref, onMounted, onUnmounted, watch } from 'vue'
import { parseFormat, parseTimeData, isSameSecond } from './index'
const props = defineProps({
  time: {
    type: [String, Number]
  },
  format: {
    type: String,
    default: 'HH:mm:ss'
  },
  autoStart: {
    type: Boolean,
    default: true
  },
  millisecond: {
    type: Boolean,
    default: false
  }
})
let timer = null
// 格式化后的时间，如"03:23:21"
const formattedTime = ref('0')
// 倒计时是否正在进行中
const runing = ref(false)
// 结束的毫秒时间戳
const endTime = ref(0)
// 剩余的毫秒时间
const remainTime = ref(0)

onMounted(() => {
  init()
})

watch(
  () => props.time,
  () => {
    reset()
  }
)

function init() {
  reset()
}

function start() {
  if (runing.value) return
  runing.value = true
  endTime.value = Date.now() + Number(remainTime.value)
  toTick()
}

function toTick() {
  macroTick()
}

function macroTick() {
  clearTimer()
  timer = setTimeout(() => {
    const remain = getRemainTime()
    setRemainTime(remain)
    if (remain !== 0) {
      macroTick()
    }
  }, 30)
}

function getRemainTime() {
  return Math.max(endTime.value - Date.now(), 0)
}

const emit = defineEmits(['change', 'finish'])

function setRemainTime(remain) {
  remainTime.value = remain

  const timeData = parseTimeData(remain)

  emit('change', timeData)
  formattedTime.value = parseFormat(props.format, timeData)
  if (remain <= 0) {
    pause()
    emit('finish')
  }
}

function reset() {
  pause()
  remainTime.value = props.time
  setRemainTime(remainTime.value)
  if (props.autoStart) {
    start()
  }
}

function pause() {
  runing.value = false
  clearTimer()
}
function clearTimer() {
  clearTimeout(timer)
  timer = null
}
onUnmounted(() => {
  clearTimer()
})
defineExpose({
  start,
  pause,
  reset
})
</script>

<template>
  <div class="count-down">
    <slot>
      <div class="count-down-text">{{ formattedTime }}</div>
    </slot>
  </div>
</template>

<style scoped lang="scss"></style>
